package com.ship.dispatch.service.impl;/*
 *@title SpDispatchSchemeExecuteServiceImpl
 *@description
 *@author yl
 *@create 2023/12/13 0013
 */

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DatePattern;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.ship.common.core.utils.StringUtil;
import com.ship.common.core.utils.StringUtils;
import com.ship.common.core.web.domain.JsonResult;
import com.ship.common.business.service.impl.BaseServiceImpl;
import com.ship.dispatch.bean.SpDispatchScheme;
import com.ship.dispatch.bean.SpDispatchSchemeExecute;
import com.ship.dispatch.bean.boats.info.*;
import com.ship.dispatch.bean.fob.SpFobBaseBean;
import com.ship.dispatch.bo.ItemStatisticsSimpleBo;
import com.ship.dispatch.bpm.service.ProcessInstanceService;
import com.ship.dispatch.bpm.utils.CalculateDateUtil;
import com.ship.dispatch.bpm.vo.dto.FormTemplate;
import com.ship.dispatch.bpm.vo.dto.TaskDto;
import com.ship.dispatch.mapper.SpDispatchSchemeExecuteMapper;
import com.ship.dispatch.mapper.SpDispatchSchemeMapper;
import com.ship.dispatch.service.SpDispatchSchemeExecuteService;
import com.ship.dispatch.service.SpInformationService;
import com.ship.dispatch.service.boats.BoatsAisMessageService;
import com.ship.dispatch.service.fob.FobBaseService;
import com.ship.dispatch.service.fob.FobService;
import com.ship.dispatch.service.shipBusiness.SmShipReportService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.DecimalFormat;
import java.text.ParseException;
import java.util.*;

import static com.ship.dispatch.util.NumberFormatUtil.decimalFormat;

@Service
public class SpDispatchSchemeExecuteServiceImpl extends BaseServiceImpl<SpDispatchSchemeExecuteMapper, SpDispatchSchemeExecute> implements SpDispatchSchemeExecuteService {

    @Autowired(required = false)
    SpDispatchSchemeExecuteMapper spDispatchSchemeExecuteMapper;

    @Autowired
    @Lazy
    private ProcessInstanceService processInstanceService;

    @Lazy
    @Autowired
    FobService fobService;

    @Autowired
    private BoatsAisMessageService boatsAisMessageService;

    @Autowired
    private SmShipReportService shipReportService;

    @Autowired
    private SpInformationService spInformationService;

    @Override
    public SpDispatchSchemeExecute getExceuteByInstanceId(String instanceId) {
        return this.baseMapper.selectOne(new LambdaQueryWrapper<SpDispatchSchemeExecute>().eq(SpDispatchSchemeExecute::getProcessInstanceId,instanceId).last("limit 1"));
    }

    @Override
    public SpFobBaseBean getAssigenersByNode(String processInstaneId, String nodeType) {
        return fobService.getAssigenersByNode(processInstaneId,nodeType);
    }

    @Override
    public JsonResult countSchemeInfo(String planYear) {
        List<Map<String,String>> list = null;
        if(planYear==null || "".equals(planYear)){
            //planYear = CalculateDateUtil.getYears(new Date());
            list = spDispatchSchemeExecuteMapper.countSchemeCount();
        }else{
            list = spDispatchSchemeExecuteMapper.countSchemeInfo(planYear);

        }
        return JsonResult.success(list);
    }

    @Override
    public List<FormTemplate> bingdFormTemplate(List<FormTemplate> templates, String key,String processInstaneId) {
        List<Long> ids = fobService.findServieData(key,processInstaneId);
        List<FormTemplate> result = new ArrayList<>();
        if(ids!=null && ids.size()>0){
            for(Long id:ids){
                for (FormTemplate template:templates){
                    FormTemplate tempTemplate = new FormTemplate();
                    BeanUtils.copyProperties(template,tempTemplate);
                    tempTemplate.setServiceId(id+"");
                    result.add(tempTemplate);
                }
            }
        }else {
            result = templates;
        }
        return result;
    }

    @Override
    public JsonResult deleteEexecute(Long id) {
        SpDispatchSchemeExecute execute = this.baseMapper.selectById(id);
        if(execute.getStatus()==0){
            // 撤回流程
            try{
                processInstanceService.cacenProcessInstance(execute.getProcessInstanceId());
            }catch (Exception e){
            }
        }
        this.baseMapper.deleteById(id);
        return JsonResult.success();
    }

    @Override
    public List<String> queryImoList(ItemStatisticsSimpleBo bo) {
        String startDate = null;
        String endDate =null;
        if (bo.getStartTime() != null){
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(bo.getStartTime());
            calendar.add(calendar.DATE, -30);
            startDate = DateUtil.format(calendar.getTime(), DatePattern.NORM_DATE_FORMATTER);
            Calendar calendar1 = Calendar.getInstance();
            calendar1.setTime(bo.getEndTime());
            calendar1.add(calendar1.DAY_OF_MONTH, 30);
            endDate = DateUtil.format(calendar1.getTime(), DatePattern.NORM_DATE_FORMATTER);
        }else {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(new Date());
            calendar.add(calendar.DATE, -30);
            startDate = DateUtil.format(calendar.getTime(), DatePattern.NORM_DATE_FORMATTER);
            Calendar calendar1 = Calendar.getInstance();
            calendar1.setTime(new Date());
            calendar1.add(calendar1.DAY_OF_MONTH, 30);
            endDate = DateUtil.format(calendar1.getTime(), DatePattern.NORM_DATE_FORMATTER);
        }
        return baseMapper.queryImoList(startDate,endDate);
    }

    @Override
    public List<QueryAisInfo> queryAisByShipName(Long id) throws ParseException {
        SpDispatchSchemeExecute spDispatchSchemeExecute = baseMapper.selectById(id);
        String startDate = null;
        String endDate = null;
        if (null != spDispatchSchemeExecute){
            if (0 == spDispatchSchemeExecute.getStatus()){
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(),DatePattern.NORM_DATETIME_FORMATTER);
                endDate = DateUtil.format(new Date(),DatePattern.NORM_DATETIME_FORMATTER);
            }else if (1 == spDispatchSchemeExecute.getStatus() || 2 == spDispatchSchemeExecute.getStatus()){
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(),DatePattern.NORM_DATETIME_FORMATTER);
                endDate = DateUtil.format(spDispatchSchemeExecute.getRealityUnloadingDate(),DatePattern.NORM_DATETIME_FORMATTER);
            }

            if (StringUtils.isNotEmpty(startDate) && StringUtils.isNotEmpty(endDate)){
                List<QueryAisInfo> aisList = boatsAisMessageService.queryAisByShipName(spDispatchSchemeExecute.getShipName(),spDispatchSchemeExecute.getImo(),startDate,endDate);
                return aisList;
            }
        }
        return null;
    }

    @Override
    public List<QueryFuelConsumptionTrendInfo> queryFuelConsumptionTrend(Long id) {
        SpDispatchSchemeExecute spDispatchSchemeExecute = baseMapper.selectById(id);
        String startDate = null;
        String endDate = null;
        if (null != spDispatchSchemeExecute) {
            if (0 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(new Date(), DatePattern.NORM_DATE_FORMATTER);
            } else if (1 == spDispatchSchemeExecute.getStatus() || 2 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(spDispatchSchemeExecute.getRealityUnloadingDate(), DatePattern.NORM_DATE_FORMATTER);
            }
            if (StringUtils.isNotEmpty(startDate) && StringUtils.isNotEmpty(endDate)){
                List<QueryFuelConsumptionTrendInfo> list = shipReportService.queryFuelConsumptionTrend(spDispatchSchemeExecute.getShipName(),startDate,endDate);
                return list;
            }
        }
        return null;
    }

    @Override
    public List<QueryEvaporationConsumptionTrendInfo> queryEvaporationConsumptionTrend(Long id) {
        SpDispatchSchemeExecute spDispatchSchemeExecute = baseMapper.selectById(id);
        String startDate = null;
        String endDate = null;
        if (null != spDispatchSchemeExecute) {
            if (0 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(new Date(), DatePattern.NORM_DATE_FORMATTER);
            } else if (1 == spDispatchSchemeExecute.getStatus() || 2 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(spDispatchSchemeExecute.getRealityUnloadingDate(), DatePattern.NORM_DATE_FORMATTER);
            }
            if (StringUtils.isNotEmpty(startDate) && StringUtils.isNotEmpty(endDate)){
                List<QueryEvaporationConsumptionTrendInfo> list = shipReportService.queryEvaporationConsumptionTrend(spDispatchSchemeExecute.getShipName(),startDate,endDate);
                return list;
            }
        }
        return null;
    }

    @Override
    public QueryShipTraceInfo queryMmsiByShipName(Long id) {
        QueryShipTraceInfo queryShipTraceInfo = new QueryShipTraceInfo();
        SpDispatchSchemeExecute spDispatchSchemeExecute = baseMapper.selectById(id);
        String mmsi = spInformationService.queryMmsiByShipName(spDispatchSchemeExecute.getShipName(),spDispatchSchemeExecute.getImo());
        if (0 == spDispatchSchemeExecute.getStatus()) {
            queryShipTraceInfo.setMmsi(mmsi);
        } else if (1 == spDispatchSchemeExecute.getStatus() || 2 == spDispatchSchemeExecute.getStatus()) {
            queryShipTraceInfo.setMmsi(mmsi);
            String startDate = DateUtil.format(spDispatchSchemeExecute.getRealityLoadingDate(), DatePattern.NORM_DATE_FORMATTER);
            String endDate = DateUtil.format(spDispatchSchemeExecute.getRealityUnloadingDate(), DatePattern.NORM_DATE_FORMATTER);
            queryShipTraceInfo.setStartDate(startDate);
            queryShipTraceInfo.setEndDate(endDate);
        }
        return queryShipTraceInfo;
    }

    @Override
    public List<BoatsEventMessageInfo> queryBoatsEventMessageById(Long id) {
        SpDispatchSchemeExecute spDispatchSchemeExecute = baseMapper.selectById(id);
        String startDate = null;
        String endDate = null;
        if (null != spDispatchSchemeExecute) {
            if (0 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(new Date(), DatePattern.NORM_DATE_FORMATTER);
            } else if (1 == spDispatchSchemeExecute.getStatus() || 2 == spDispatchSchemeExecute.getStatus()) {
                startDate = DateUtil.format(spDispatchSchemeExecute.getSchemeDeliveryTime(), DatePattern.NORM_DATE_FORMATTER);
                endDate = DateUtil.format(spDispatchSchemeExecute.getRealityUnloadingDate(), DatePattern.NORM_DATE_FORMATTER);
            }
            if (StringUtils.isNotEmpty(startDate) && StringUtils.isNotEmpty(endDate)){
                List<BoatsEventMessageInfo> eventNessageList = baseMapper.queryBoatsEventMessageById(spDispatchSchemeExecute.getImo(),startDate,endDate);
                if (CollectionUtil.isNotEmpty(eventNessageList)){
                    eventNessageList.forEach(item -> {
                        item.setEventMessage(getEventMessage(item.getEventType()));
                    });
                }
                return eventNessageList;
            }
        }
        return null;
    }

    @Override
    public Integer queryTransportShipNumber() {
        return baseMapper.queryTransportShipNumber();
    }

    @Override
    public String queryCarryOutNumber() {
        BigDecimal carryOutNumber = BigDecimal.ZERO;
        List<SpDispatchSchemeExecute> executeList = baseMapper.queryCarryOutNumber();
        if (CollectionUtil.isNotEmpty(executeList)){
            for (SpDispatchSchemeExecute spDispatchSchemeExecute : executeList) {
                if (spDispatchSchemeExecute.getQuantityUnit() == 1){
                    BigDecimal subtract = spDispatchSchemeExecute.getRealityLoadingCapacity().subtract(new BigDecimal(22.5));
                    carryOutNumber = carryOutNumber.add(subtract.multiply(new BigDecimal(0.475)));
                }else if (spDispatchSchemeExecute.getQuantityUnit() == 2){
                    carryOutNumber = carryOutNumber.add(spDispatchSchemeExecute.getRealityLoadingCapacity().multiply(new BigDecimal(0.475)));
                }else if (spDispatchSchemeExecute.getQuantityUnit() == 3){
                    carryOutNumber = carryOutNumber.add(spDispatchSchemeExecute.getRealityLoadingCapacity());
                }
            }
        }
        if (carryOutNumber.compareTo(BigDecimal.ZERO) > 0){
            BigDecimal result = carryOutNumber.divide(new BigDecimal(10000));
            DecimalFormat decimalFormat = new DecimalFormat("#,###.###");
           return decimalFormat.format(result.setScale(0, RoundingMode.HALF_UP));
        }
        return carryOutNumber.toString();
    }

    @Override
    public BigDecimal getPaymentAmount(String proceeInstanceId, Object port) {
        return baseMapper.getPaymentAmount(proceeInstanceId, port);
    }

    @Override
    public BigDecimal getPaymentAmountUn(String proceeInstanceId, Object port) {
        return baseMapper.getPaymentAmountUn(proceeInstanceId, port);
    }

    private String getEventMessage(String eventType) {
        String eventMessage = null;
        switch (eventType) {
            case "1":
                eventMessage = "航速变化事件";
                break;
            case "2":
                eventMessage = "航行状态变化事件";
                break;
            case "3":
                eventMessage = "吃水变化事件";
                break;
            case "4":
                eventMessage = "海区穿行事件";
                break;
            case "5":
                eventMessage = "航行异常事件";
                break;
            case "6":
                eventMessage = "恶劣天气事件";
                break;
            case "7":
                eventMessage = "进出港事件";
                break;
            default:
                eventMessage = "";
        }
        return eventMessage;
    }
}
